{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Ex1: Ring Slot"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The Vector Fitting feature is demonstrated using the *ring slot* example network from the scikit-rf `data` folder. Additional explanations and background information can be found in the [Vector Fitting tutorial](../../tutorials/VectorFitting.ipynb)."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as mplt\n",
    "import numpy as np\n",
    "\n",
    "import skrf"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "To create a `VectorFitting` instance, a `Network` containing the frequency responses of the N-port is passed. In this example the *ring slot* is used, which can be loaded directly as a `Network` from scikit-rf:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "nw = skrf.data.ring_slot\n",
    "vf = skrf.VectorFitting(nw)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Now, the vector fit can be performed. The number of poles has to be specified, which depends on the *behaviour* of the responses. A smooth response would only require very few poles (2-5). In this case, 3 real poles are sufficient:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "vf.vector_fit(n_poles_real=3, n_poles_cmplx=0)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "As printed in the logging output (not shown), the pole relocation process converged quickly after just 5 iteration steps. This can also be checked with the convergence plot:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "vf.plot_convergence()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The fitted model parameters are now stored in the class attributes `poles`, `residues`, `proportional_coeff` and `constant_coeff` for further use. To verify the result, the model response can be compared to the original network response. One option is to analyze the rms error magnitude, which should be smaller than 0.05 for a good fit:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "vf.get_rms_error()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "As the model will return a response at any given frequency, it makes sense to also manually check its response outside the frequency range of the original samples by plotting it at lower and higher frequencies:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "freqs1 = np.linspace(0, 200e9, 201)\n",
    "fig, ax = mplt.subplots(2, 2)\n",
    "fig.set_size_inches(12, 8)\n",
    "vf.plot_s_mag(0, 0, freqs1, ax=ax[0][0]) # plot s11\n",
    "vf.plot_s_mag(1, 0, freqs1, ax=ax[1][0]) # plot s21\n",
    "vf.plot_s_mag(0, 1, freqs1, ax=ax[0][1]) # plot s12\n",
    "vf.plot_s_mag(1, 1, freqs1, ax=ax[1][1]) # plot s22\n",
    "fig.tight_layout()\n",
    "mplt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "To use the model in a circuit simulation, an equivalent circuit can be created based on the fitting parameters. This is currently only implemented for SPICE, but the structure of the equivalent circuit can be adopted to any kind of circuit simulator. Attention: A UserWarning about a non-passive fit was printed (see output of vector_fit() above). The assessment and enforcement of model passivity is described in more detail in [this example](./vectorfitting_ex4_passivity.ipynb), which is important for certain use cases in circuit simulators, i.e. transient simulations."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "`vf1.write_spice_subcircuit_s('/home/vinc/Desktop/ring_slot.sp')`"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "For a quick test, the subcircuit is included in a schematic in [QUCS-S](https://ra3xdh.github.io/) for AC simulation and S-parameter calculation based on the port voltages and currents (see the equations):\n",
    "<img src=\"./ngspice_ringslot_schematic.svg\" />\n",
    "\n",
    "The simulation outputs from [ngspice](http://ngspice.sourceforge.net/) compare well to the plots above:\n",
    "<img src=\"./ngspice_ringslot_sp_mag.svg\" />\n",
    "\n",
    "<img src=\"./ngspice_ringslot_sp_smith.svg\" />"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.8.8"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 4
}
